/*
 * --------------------------------------------------------------------------------
 * JavaScript 公共基础工具
 * --------------------------------------------------------------------------------
 * author:chenyang
 * updatetime:20160222
 * --------------------------------------------------------------------------------
 */
(function(window, undefined) {

    var Cy = {


            /*
             *--------------------------------------------------------------------------------
             * _firstChild 获取第一个子节点
             * --------------------------------------------------------------------------------
             * obj   : 对象
             */
            _firstChild: function(obj) {
                return obj.firstElementChild || obj.firstChild;
            },

            /*
             *--------------------------------------------------------------------------------
             * _lastChild 获取最后一个子节点
             * --------------------------------------------------------------------------------
             * obj   : 对象
             */
            _lastChild: function(obj) {
                return obj.lastElementChild || obj.lastChild;
            },

            /*
             *--------------------------------------------------------------------------------
             * _previousSibling 获取上一个子节点
             * --------------------------------------------------------------------------------
             * obj   : 对象
             */
            _previousSibling: function(obj) {
                return obj.previousElementSiblings || obj.previousSibling;
            },

            /*
             *--------------------------------------------------------------------------------
             * _nextSibling 获取下一个子节点
             * --------------------------------------------------------------------------------
             * obj   : 对象
             */
            _nextSibling: function(obj) {
                return obj.nextElementSibling || obj.nextSibling;
            },

            /*
             *--------------------------------------------------------------------------------
             * _getVieW 获得可视区域的宽度
             * --------------------------------------------------------------------------------
             */
            _getVieW: function() {
                return document.documentElement.clientWidth || document.body.clientWidth;
            },

            /*
             *--------------------------------------------------------------------------------
             * _getVieH 获得可视区域的高度
             * --------------------------------------------------------------------------------
             */
            _getVieH: function() {
                return document.documentElement.clientHeight || document.body.clientHeight;
            },

            /*
             *--------------------------------------------------------------------------------
             * _width 获得元素宽度
             * --------------------------------------------------------------------------------
             */
            _width: function(obj) {
                return obj.offsetWidth;
            },

            /*
             *--------------------------------------------------------------------------------
             * _height 获得元素高度
             * --------------------------------------------------------------------------------
             */
            _height: function(obj) {
                return obj.offsetHeight;
            },

            /*
             *--------------------------------------------------------------------------------
             * _left 获得元素left值
             * --------------------------------------------------------------------------------
             */
            _left: function(obj) {
                return obj.offsetLeft;
            },

            /*
             *--------------------------------------------------------------------------------
             * _top 获得元素top值
             * --------------------------------------------------------------------------------
             */
            _top: function(obj) {
                return obj.offsetTop;
            },


            /*
             *--------------------------------------------------------------------------------
             * _scrollLeft 获得元素左侧隐藏值
             * --------------------------------------------------------------------------------
             */
            _scrollLeft: function() {
                return document.body.scrollLeft || document.documentElement.scrollLeft;
            },


            /*
             *--------------------------------------------------------------------------------
             * _scrollTop 获得元素顶部隐藏值
             * --------------------------------------------------------------------------------
             */
            _scrollTop: function() {
                return document.body.scrollTop || document.documentElement.scrollTop;
            },


            /*
             *--------------------------------------------------------------------------------
             * _getByStyle 获得元素top值
             * --------------------------------------------------------------------------------
             */
            _getByStyle: function(obj, attr) {
                if (obj.currentStyle) {
                    return obj.currentStyle[attr];
                } else {
                    return getComputedStyle(obj, false)[attr];
                }
            },


            /*
             *--------------------------------------------------------------------------------
             * _hasClass 判断元素是否有某个class
             * --------------------------------------------------------------------------------
             */
            _hasClass: function(obj, sClass) {
                return obj.className.match(new RegExp('(\\s|^)' + sClass + '(\\s|$)'));
            },


            /*
             *--------------------------------------------------------------------------------
             * _addClass 给元素添加一个class
             * --------------------------------------------------------------------------------
             */
            _addClass: function(obj, sClass) {
                if (!this._hasClass(obj, sClass)) obj.className += " " + sClass;
            },


            /*
             *--------------------------------------------------------------------------------
             * _removeClass 删除一个class
             * --------------------------------------------------------------------------------
             */
            _removeClass: function(obj, sClass) {
                if (this._hasClass(obj, sClass)) {
                    var reg = new RegExp('(\\s|^)' + sClass + '(\\s|$)');
                    obj.className = obj.className.replace(reg, '');
                }
            },

            /*
             *--------------------------------------------------------------------------------
             * _addEvent 添加事件
             * --------------------------------------------------------------------------------
             * obj   : 对象
             * sEvent: 事件类型
             * fn    : 回调
             */
            _addEvent: function(obj, sEvent, fn) {
                if (window.attachEvent) {
                    obj.attachEvent("on" + sEvent, function() {
                        fn.call(obj);
                    });
                } else {
                    obj.addEventListener(sEvent, fn, false);
                }
            },

            /*
             *--------------------------------------------------------------------------------
             * _removeEvent 移除事件
             * --------------------------------------------------------------------------------
             * obj   : 对象
             * sEvent: 事件类型
             * fn    : 回调
             */
            _removeEvent: function(obj, sEvent, fn) {
                if (window.detachEvent) {
                    obj.detachEvent("on" + sEvent, function() {
                        fn.call(obj);
                    });
                } else {
                    obj.removeEventListener(sEvent, fn, false);
                }
            },

            /*
             *--------------------------------------------------------------------------------
             * _isWindow 判断是否是window对象
             * --------------------------------------------------------------------------------
             * obj   : 对象
             */
            _isWindow: function(obj) {
                return obj != null && obj === obj.window;
            },

            /*
             *--------------------------------------------------------------------------------
             * _isPlainObject 判断是否是json对象
             * --------------------------------------------------------------------------------
             * obj   : 对象
             */
            _isPlainObject: function(obj) {

                if (typeof(obj) !== "object" || obj.nodeType || this._isWindow(obj)) {
                    return false;
                }

                if (obj.constructor && !{}.hasOwnProperty.call(obj.constructor.prototype, "isPrototypeOf")) {
                    return false;
                }
                return true;
            },

            /*
             *--------------------------------------------------------------------------------
             * _range 限制范围
             * --------------------------------------------------------------------------------
             * min   : 最小值
             * max   : 最大值
             * val   : 当前值
             */
            _range: function(min, max, val) {
                return val < min ? min : (val > max ? max : val);
            },

            /*
             *--------------------------------------------------------------------------------
             * _getArryMin 获取数组最小值
             * --------------------------------------------------------------------------------
             * array   : 数组
             */
            _getArryMin: function(arr) {
                return Math.min.apply(Math, arr);
            },

            /*
             *--------------------------------------------------------------------------------
             * _getArryMax 获取数组最大值
             * --------------------------------------------------------------------------------
             * array   : 数组
             */
            _getArryMax: function(arr) {
                return Math.max.apply(Math, arr);
            },

            /*
             *--------------------------------------------------------------------------------
             * _getRandom 获取一个指定范围的随机数(含min/max)
             * --------------------------------------------------------------------------------
             * min   : 最小值
             * max   : 最大值
             */
            _getRandom: function(min, max) {
                return Math.round(Math.random() * (max - min)) + min;
            },

            /*
             *--------------------------------------------------------------------------------
             * _getRandomArry 获取一个指定范围的一组随机数(含min/max，且不重复)
             * --------------------------------------------------------------------------------
             * min   : 最小值
             * max   : 最大值
             */
            _getRandomArry: function(min, max, num) {
                var array = [];
                while (array.length != num) {
                    var random = this._getRandom(min, max);
                    if (!this._isContain(array, random)) {
                        array.push(random);
                    }
                }
                return array;
                //return Math.round(Math.random() * (max - min)) + min;
            },

            /*
             *--------------------------------------------------------------------------------
             * _isContain 判断数组是否包含指定的元素
             * --------------------------------------------------------------------------------
             * array   : 数组
             * element : 元素
             */
            _isContain: function(array, element) {
                for (var i = 0; i < array.length; i++) {
                    if (array[i] == element) {
                        return true;
                    }
                }
                return false;
            },

            /*
             *--------------------------------------------------------------------------------
             * _ArrayNoRepeat 数组去除重复元素
             * --------------------------------------------------------------------------------
             * array   : 数组
             * element : 元素
             */
            _ArrayNoRepeat: function(array) {
                var result = [],
                    hash = {};
                for (var i = 0, elem;
                    (elem = arr[i]) != null; i++) {
                    if (!hash[elem]) {
                        result.push(elem);
                        hash[elem] = true;
                    }
                }
                return result;
            },

            /*
             *--------------------------------------------------------------------------------
             * _extend 深拷贝对象(json or dom)
             * --------------------------------------------------------------------------------
             * array   : 数组
             */
            _extend: function(desc, target, isOverride) {
                for (var i in target) {
                    if (target.hasOwnProperty(i) && (!desc.hasOwnProperty(i) || isOverride)) desc[i] = target[i];
                }
            }


        }
        //挂载到window上
    window.Cy = Cy;

})(window, undefined);
